home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Apple II Magazines (PO)
/
Nibble Volume 10, No. 04 (1989-04)(MicroSPARC)(Side A).zip
/
Nibble Volume 10, No. 04 (1989-04)(MicroSPARC)(Side A).po
/
SC.SYSTEM.S
< prev
next >
Wrap
Text File
|
1996-12-24
|
15KB
|
631 lines
****************************
* *
* SC.SYSTEM SOURCE CODE *
* BY SEAN NOLAN *
* (C) COPYRIGHT 1989 *
* MICROSPARC, INC. *
* CONCORD, MA 01742 *
* MERLIN PRO assembler *
* *
****************************
ORG $1000 code runs at $1000 but
;is loaded at $2000 by ProDOS
TYP $FF save as a system file
******************************** equates
READY = 3 - if date on disk is updated
DAY = 4 | ProDOS date bytes are broken |
MONTH = 5 | up into seperate Day, Month, |
YEAR = 6 | and Year bytes for clarity. |
WNDLEFT = $20 left edge of window
CH = $24 cursor horizontal
A1L = $3C
A1H = $3D
IN2 = $280
RESET = $3F2
MLI = $BF00 ProDOS entry point
CALLCLOCK = $BF06 JMP to ProDOS clock code
DEVNUM = $BF30 number of last disk accesssed
DATE = $BF90 date stored here in packed format
TIME = $BF92 time stored in minutes : hours
CMDADR = $BF9C Address+6 of last MLI call
KEYBOARD = $C000 read keyboard
STROBE = $C010 eat keypress
WRITEBSR1 = $C089 write language card bank 1
NORMROM = $C08A turn off language card RAM
SETPWRC = $FB6F fix power-up byte
GOODF8 = $FBB3 identifies II+ vs. IIe/IIc
COUT = $FDED print character
PRBYTE = $FDDA print 2-digit hex value
VTABZ = $FC24 calculate text output for row A
HOME = $FC58 clear screen
RDKEY = $FD0C get key with blinking cursor
SETKBD = $FE89 IN#0
SETVID = $FE93 PR#0
******************************** initialization code
JMP START+$1000
DFB $EE,$EE indicate startup protocol
DFB 33 size of startup buffer
STARTUP DFB 12 length of startup name
ASC "BASIC.SYSTEM" default startup program
DS STARTUP+33-*
DFB 0
*** relocate ourselves down to $1000
START LDY #0
LDX #5 copy 5 pages of code
:a LDA $2000,Y
:b STA $1000,Y
INY
BNE :a
INC :a+$1002
INC :b+$1002
DEX
BNE :a
JMP START2 jump to relocated code
START2 LDX STARTUP put 00 at the end of the
TYA ; startup name so that
STA STARTUP+1,X PRINTAY can print it.
JSR SETKBD IN#0
JSR SETVID PR#0
***** Set Prefix to this volume
LDA DEVNUM get #of last device accessed
STA ONLINEn enter with device number in A
JSR MLI
DFB $C5
DA ONLINEp
LDY IN2+1 insert a slash before the name
INY
TYA
AND #$0F
STA IN2
LDA #'/'
STA IN2+1
JSR MLI set the prefix
DFB $C6
DA SETPFXp
***** Copy the soft clock routine into ProDOS
LDA #$60 Disable the Softclock routine if it
STA CALLCLOCK is going already.
LDA CALLCLOCK+1
STA A1L
LDA CALLCLOCK+2
STA A1H
BIT WRITEBSR1 Turn on language card
BIT WRITEBSR1
LDY #SOFTEND-SOFT (size of Softclock)
:loop1 LDA SOFT,Y
STA (A1L),Y
DEY
BPL :loop1
BIT NORMROM turn off language card
**** get date from file on disk
LDA #10 number of parameters
LDX #$C4 MLI command number
JSR GETINFO
LDX #3 move 4 bytes into global page
:loop2 LDA MODDATE,X
STA DATE,X
DEX
BPL :loop2
TAY ;if the DATE byte is 0, there is no date,
BNE :a so initialize it to February 1, 1989
LDA #$41
STA DATE
LDA #$B2
STA DATE+1
INX ;make X=0
:a STX READY indicate whether date needs to be saved on disk
;if 0, it needs saving. If $FF, all is OK
LDA DATE+1 unpack the date bytes in the global page
LSR ;into seperate day, month, and time bytes
STA YEAR Year is high 7 bits of DATE+1
LDA DATE
ROR ;roll bit 0 of DATE+1 into DATE
LSR ;shift 4 more times for month
LSR
LSR
LSR
STA MONTH
LDA DATE low 5 bits are day
AND #%11111
STA DAY
***** install reset trap
LDA #<RESTART
STA RESET
LDA #>RESTART
STA RESET+1
JSR SETPWRC fix power-up byte
******************************** main menu
RESTART LDX #$FF Re-enter here after errors
TXS ;and control-RESET
CLD
JSR CLOSEALL
JSR HOME
JSR ROW40
LDA #11
STA CH
LDA #>:text1
LDY #<:text1
JSR PRINTAY
JSR ROW40
LDA #6
STA WNDLEFT
LDA #>:text2
LDY #<:text2
JSR PRINTAY
LDA #>STARTUP+1
LDY #<STARTUP+1
JSR PRINTAY
STA WNDLEFT (A=0 here)
:next JSR PRINTDT print updated date/time
:key LDA KEYBOARD wait for a key
BPL :key
STA STROBE
CMP #"`" convert lower to upper case
BCC :ok
SBC #32
:ok LDX #7 Try to match keypress
:loop CMP :keys,X with list of valid ones.
BEQ :match
DEX
BPL :loop
BMI :next if bad keypress, get another
:match TXA
ASL
TAX
LDA :addr,X
STA :mod+1
LDA :addr+1,X
STA :mod+2
:mod JSR $FFFF self-modified
LDA MONTH rebuild DATE bytes in the ProDOS global
ASL ;page in case we changed them by pressing
ASL ;an arrow key
ASL
ASL
ASL
ORA DAY
STA DATE carry holds high bit of month
LDA YEAR
ROL
STA DATE+1
BCC :next branch always
:text1 DFB $8A
ASC "Apple ][ Softclock"
DFB $8D,$8D
ASC "BY SEAN NOLAN (C)1989 MICROSPARC, INC."
DFB $8D,0
:text2 DFB $8D,$8D,$8D,$8D,$8D,$8D,$8D
ASC "Arrow keys change the date"
DFB $8D,$8D
ASC "T - Change the time"
DFB $8D,$8D
ASC "S - Save date/time to disk"
DFB $8D,$8D
ASC "Q - Quit"
DFB $8D,$8D
ASC "R - Run "
DFB 0
:keys DFB $95,$88,$8A,$8B,"T","S","Q","R"
:addr DA INCDAY next day
DA DECDAY previous day
DA INCMONTH next month
DA DECMONTH previous month
DA GETTIME input time
DA SETINFO save date to disk
DA QUIT quit code
DA GOBASIC go to BASIC.SYSTEM
******************************** change the date
DECDAY LSR READY flag that date has changed
DEC DAY
BNE :a
JSR DECMONTH
LDX MONTH
LDA DAYS-1,X
STA DAY
:a RTS
DECMONTH LSR READY
DEC MONTH backup to previous month
BNE :a
LDA #12
STA MONTH December
DEC YEAR backup to previous year
BPL :a fix year at the turn of the century
LDA #99
STA YEAR
:a RTS
INCDAY LSR READY
LDX MONTH
LDA DAY
INC DAY increment the day
CMP DAYS-1,X if we were not at monthly limit,
BNE :a then exit.
LDA #1
STA DAY Otherwise, set day to 1
JSR INCMONTH and inc the month
:a RTS
INCMONTH LSR READY
INC MONTH
LDA MONTH
CMP #13
BNE :a
LDA #1
STA MONTH
INC YEAR
LDA YEAR
EOR #99 fix year at the turn of the century
BNE :a
STA YEAR
:a RTS
DAYS DFB 31,29,31,30,31,30
DFB 31,31,30,31,30,31
******************************** change the time
GETTIME LDA #7 position cursor at CV=7, CH=23
JSR VTABZ
LDA #23
STA CH
LDX #5 get up to 4 keypresses
:a JSR RDKEY get a keypress (with cursor visable)
CMP #$8D skip ahead if RETURN...
BEQ :c
CMP #$9B ...or cancel entirely if ESCAPE
BEQ :e
CMP #"0" reject other keys except digits
BCC :a
CMP #"9"+1
BCS :a
:b LSR READY flag that time has changed
JSR COUT if digit gotten, print it
DEX
LDA #":"
CPX #3 after getting 2nd character, skip the colen
BEQ :b
TXA
BNE :a
;desired time is now on the screen
:c LDA $780+23 pick the hour off of the screen
LDY $780+24 and convert to a single byte
JSR CONVERT
CPX #24 make sure hour is in range
BCS :d
STX TIME+1
:d LDA $780+26 do the same for the minutes
LDY $780+27
JSR CONVERT
CPX #60 make sure minutes is in range
BCS :e
STX TIME
:e RTS
* Enter with ASCII values for number in A (high decimal digit)
* and Y (low decimal digit). Exit with hex byte in X.
* Called only by GETTIME
CONVERT ASL ;shift high digit into high nybble
ASL
ASL
ASL
STA A1L
TYA ;isolate low digit
AND #$0F
ORA A1L combine with high - now have BCD value.
SED ;convert BCD Accumulator to hex X register
LDX #$FF
SEC
:loop SBC #1
INX
BCS :loop
CLD
RTS
******************************** store date/time to disk
SETINFO LDX #3 move date & time to DTplist
:loop LDA DATE,X
STA MODDATE,X
DEX
BPL :loop
STX READY flag that date saved
LDA #7 number of parameters
LDX #$C3 MLI command number for set file info
GETINFO STA :p this code is called on startup to read
STX :a the date stored in the MOD TIME field.
JSR MLI
:a DFB 0
DA :p
JMP ERROR?
*** ProDOS parameter list for date and time
*
* Used whenever the time is written to or read from the
* disk. The time is stored as the MOD TIME field of the
* file "SC.SYSTEM" on the disk.
:p DFB 0 self-modified
DA NAME pointer to name
DFB $C3 access code
DFB $FF file type code
DA 0 aux type
DFB $02 storage type
DA 0 blocks used
MODDATE DA 0 mod date returned here
DA 0 mod time returned here
DFB 0,0,0,0 create date & time
NAME DFB 9 (leading length byte)
ASC "SC.SYSTEM"
******************************** Quit
QUIT JSR TURNON Save date to disk
;and turn on Softclock
JSR MLI quit
DFB $65
DA :a
:a DFB 4
DFB 0,0,0,0,0,0
TURNON BIT READY if date or time has changed
BMI :ok then update date on disk.
JSR SETINFO
:ok LDA #$4C change entering RTS to a JMP
STA CALLCLOCK to turn on Softclock
RTS
******************************** Go to BASIC
* (or any other SYSTEM program whose name was
* placed in the startup buffer of this program)
GOBASIC JSR MLI open the startup file
DFB $C8
DA :open
JSR ERROR?
LDA :on copy reference number
STA :rn
JSR MLI read it in
DFB $CA
DA :read
JSR ERROR?
JSR CLOSEALL close it
JSR TURNON Save date to disk
;and turn on Softclock
JMP $2000 Jump to next system program
:open DFB 3
DA STARTUP name of program to open
DA $800 i/o buffer
:on DFB 0 reference number result here
:read DFB 4
:rn DFB 0 reference number
DA $2000 put system program here
DA $9F00 request largest possible size
DA 0 length read in returned here
******************************** character output
**** Print string whose address is passed in AY
**** Always exit with A=0
PRINTAY STA A1H
STY A1L
LDY #0
:loop LDA (A1L),Y
BEQ :rts
ORA #$80
BIT GOODF8 if running on a II or II+,
BPL :ok change lower-case to upper.
CMP #$E0
BCC :ok
SBC #32
:ok JSR COUT
INY
BNE :loop always
:rts RTS
**** Print 40 underlines
ROW40 LDX #40
LDA #"_"
:loop JSR COUT
DEX
BNE :loop
RTS
******************************** the soft-clock routine
* This is installed deep into the bowels of ProDOS, and
* hangs around long after this program is only a memory.
SOFT CLD
SEC ;Only inc the time if a close
LDA CMDADR file MLI call is in progress.
SBC #3 This way programs that call
STA A1L GETTIME continuously won't make
LDA CMDADR+1 time race by.
SBC #0
STA A1H
LDX #0
LDA (A1L,X)
CMP #$CC if MLI call is not CLOSE, exit
BNE :exit
INC TIME inc minute by 1
LDA TIME
EOR #60
BNE :exit
STA TIME if even hour reached
INC TIME+1
LDA TIME+1
EOR #24 If even day reached go back
BNE :exit to 0:00. Sorry, the clock
STA TIME+1 will not change the date at
:exit CLC ;midnight.
SOFTEND RTS
******************************** Print date/time
PRINTDT LDA #12
STA CH
LDA #7
JSR VTABZ
LDX DAY print day
JSR :printdec
LDA #"-"
JSR COUT
LDA MONTH get month...
ASL
ADC MONTH ...times 3
TAX
LDY #3 print 3 characters for month
:loop1 LDA :months-3,X
JSR COUT
INX
DEY
BNE :loop1
LDA #"-"
JSR COUT
LDX YEAR print year
JSR :printdec
INC CH
INC CH
LDX TIME+1 print hours
JSR :printdec
LDA #":"
JSR COUT
LDX TIME print minutes
:printdec SED ;convert HEX > BCD
LDA #$99 enter with value to convert in X
:loop2 CLC ;exits with BCD byte in Accumulator
ADC #1
DEX
BPL :loop2
CLD
JMP PRBYTE print it
:months ASC "JANFEBMARAPRMAYJUN"
ASC "JULAUGSEPOCTNOVDEC"
******************************** error trapper
ERROR? BCC :rts
PHA ;remember error number
JSR HOME
LDA #11
STA CH
JSR VTABZ
LDA #>:text
LDY #<:text
JSR PRINTAY
PLA ;get error number
JSR PRBYTE
INC CH
JSR RDKEY
JMP RESTART
:rts RTS
:text ASC "ProDOS error $"
DFB 0
ONLINEp DFB 2 online parameter list
ONLINEn DFB 0 device number
DA IN2+1
SETPFXp DFB 1 set prefix parameter list
DA IN2
CLOSEALL JSR MLI close all files
DFB $CC
DA :a
RTS
:a DFB 1,0